/*
 * @Author       : Bing Chen chenbing@iocharger.com
 * @Date         : 2024-05-20 15:34:07
 * @LastEditors  : Bing Chen chenbing@iocharger.com
 * @LastEditTime : 2025-03-15 12:49:16
 * @FilePath     : \openchaoji-corelib\secc\include\OpenChaoJi_secc_context.h
 * @Description  : 本文件定义SECC模块的上下文相关信息
 *                 上下文用于所有模块通信, 上下文与SECC一一对应, 是所有模块的唯一句柄
 *
 * Copyright (c) 2025 OpenChaoJi
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the icense for the specific language governing permissions and
 * limitations under the License.
 *
 */

#ifndef __OPENCHAOJI_SECC_CONTEXT_H__
#define __OPENCHAOJI_SECC_CONTEXT_H__

#include "../../shared/include/OpenChaoJi_shared.h"

#include "../utility/OpenChaoJi_secc_utility_linkage.h"
#include "../utility/OpenChaoJi_secc_utility_pilot.h"
#include "../utility/OpenChaoJi_secc_utility_session.h"

#include "../gbt27930/OpenChaoJi_secc_gbt27930_def.h"
#include "../gbt27930/OpenChaoJi_secc_gbt27930_a.h"
#include "../gbt27930/OpenChaoJi_secc_gbt27930_b.h"

/**
 * 上下文句柄为所有模块的唯一句柄
 * 每个模块允许在此添加自己的context和create信息
 * 各模块仅允许访问自己模块的context信息, 禁止直接使用其他模块的context内部信息(必须通过接口调用)
 * Alpha版本时context信息对外可以访问, 后续切换Beta版本时各模块的context信息将编译隐藏, 所以各模块开发者务必遵守本约定, 防止后续调整引起大的改动
*/
struct OpenChaoJi_secc_context {

    /**
     * 标识号, 用于debug打印, 一般是序号
    */
    int tag;

    /**
     * 应用启动创建上下文时, 各集成厂家可以传一个与本库无关的静态数据指针, 本库将保存该指针
     * 当app/hal层使用上下文时, 各集成厂家可以自行读取该数据
     * 一般最佳实践是传递本secc对应的索引序号, IO-MAP等
    */
    OpenChaoJi_hal_handle hal_handle;

    /* 当前使用的secc系统 */
    enum OpenChaoJi_secc_gbt27930_type secc_gbt27930_type;
    struct OpenChaoJi_secc_gbt27930_system * secc_gbt27930_system;

    /* utility层句柄, pilot负责18487附录2/3的导引流程处理, session负责27930的状态切换 */
    struct OpenChaoJi_secc_context_utility_pilot * context_pilot;
    struct OpenChaoJi_secc_context_utility_session* context_session;

    /* 系统的当前运行所在模块状态 和 该模块下的子状态 */
    int current_module_status_id;
    /* 系统进入当前运行状态的时间戳 */
    uint32_t current_status_ticks;

    /* 当前系统的实时运行数据 */
    union {
        struct OpenChaoJi_secc_gbt27930_a_data * a;
        struct OpenChaoJi_secc_gbt27930_b_data * b;
    } running_data;

    /* app层当前是否允许充电 */
    int app_permit_charge;
};

/**
 * 创建上下文所需要的必要信息
*/
struct OpenChaoJi_secc_context_create_info {

    /**
     * 标识号, 用于debug打印, 一般是序号
    */
    int tag;

    /**
     * 应用启动创建上下文时, 各集成厂家可以传一个与本库无关的静态数据指针, 本库将保存该指针
     * 当app/hal层使用上下文时, 各集成厂家可以自行读取该数据
     * 一般最佳实践是传递本secc对应的索引序号, IO-MAP等
    */
    OpenChaoJi_hal_handle hal_handle;

    /**
     * 本SECC使用的系统类型, 目前仅支持A/B两类
    */
    enum OpenChaoJi_secc_gbt27930_type secc_gbt27930_type;

    /**
     * utility层初始化信息, pilot负责18487附录2/3的导引流程处理, session负责27930的状态切换
    */
    struct OpenChaoJi_secc_create_info_utility_pilot pilot;
    struct OpenChaoJi_secc_create_info_utility_session session;
};

/**
 * 系统对外提供的状态信息
*/
struct OpenChaoJi_secc_context_status {
    /**
     * 当前状态
    */
    int current_module_status_id;

    /**
     * 需求电流值，精度0.1A
    */
    uint16_t demand_current;

    /**
     * 需求电压值，精度0.1V
    */
    uint16_t demand_voltage;

    /**
     * 当前SOC  精度0.1%
    */
    uint16_t soc;

    /**
     * 剩余估算时间 精度1min
    */
    uint16_t remain_time;

    /**
     * 扩展车辆识别码 EVIN
    */
    uint8_t evin[17];

    /**
     * 预充状态
    */
    uint8_t precharge_status;

    /**
     * 添加其它状态：导引状态、停机原因等
    */
};

/**
 * @brief: 初始化上下文, 每一把枪注册一个上下文, 所以本项目支持不同类型系统混合使用
 * @param {OpenChaoJi_secc_context_create_info *} info
 * @return {*}
 */
struct OpenChaoJi_secc_context * OpenChaoJi_secc_create_context(const struct OpenChaoJi_secc_context_create_info * info);

/**
 * @brief: 销毁一个上下文
 * @param {OpenChaoJi_secc_context *} context
 * @return {*}
 */
void OpenChaoJi_secc_destroy_context(struct OpenChaoJi_secc_context * context);

/**
 * @brief: 系统服务, 定时触发
 *         注意, 由于兼容非系统方式实现, 所以本项目所有方法默认处于同一线程, 如厂家通过操作系统实现, 厂家需要保证线程安全
 * @param {OpenChaoJi_secc_context *} context
 * @return {*}
 */
void OpenChaoJi_secc_service(struct OpenChaoJi_secc_context * context);



#endif
